/*
 * @Author: your name
 * @Date: 2022-01-01 01:04:28
 * @LastEditTime: 2022-01-02 13:27:53
 * @LastEditors: Please set LastEditors
 * @Description: 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
 * @FilePath: \json-serveg:\桌面2\TypeScript\part2\src\moduls\snake.ts
 */
class Snake{
    // //表示蛇头的元素
    // header:HTMLElement
    // //蛇的身体(包括蛇头)
    // bodies:HTMLCollection
    // //获取蛇的容器
    // element:HTMLElement


    // constructor(){
    //     this.element =  document.getElementById('snake')!

    //     this.header = document.querySelector('#snake > div')!
    //     //身体赋值
    //     this.bodies = document.getElementById('snake')!.getElementsByTagName('div')
    // }
     // 表示蛇头的元素
     header: HTMLElement;
     // 蛇的身体（包括蛇头）
     bodies: HTMLCollection;
     // 获取蛇的容器
     element: HTMLElement;
 
     constructor() {
         this.element = document.getElementById('snake')!
         this.header = document.querySelector('#snake > div') as HTMLElement;
         this.bodies = this.element.getElementsByTagName('div');
     }


    //获取蛇头的坐标
    get x(){
        return this.header.offsetLeft
    }

    get y(){
        return this.header.offsetTop
    }

    //设置蛇头的坐标
    set x(value){
        //如果新值和旧值一样,直接返回
        if (this.x === value) {
            return
        }
        //判断是否撞墙
        if (value < 0 || value > 290) {
            throw new Error("蛇撞墙了");
            
        }
        //修改X时,是在修改水平坐标,蛇在左右移动,蛇在向左移动时,不能向右掉头,反之亦然
        if (this.bodies[1] && (this.bodies[1] as HTMLElement).offsetLeft === value) {
            // console.log('水平方向发生了掉头');
            //如果发生了掉头,让蛇向反方向继续移动
            if (value > this.x) {
                value = this.x - 10
            } else {
                value = this.x + 10
            }


            
        }


         // 移动身体
         this.moveBody();

        this.header.style.left = value +'px'
        //检查有没有撞到自己
        this.checkHeaderBody()
    }

    set y(value){
        //如果新值和旧值一样,直接返回
        if (this.y === value) {
            return
        }
        //判断是否撞墙
        if (value < 0 || value > 290) {
            throw new Error("蛇撞墙了");
            
        }
        //修改X时,是在修改水平坐标,蛇在上下移动,蛇在向下移动时,不能向上掉头,反之亦然
        if (this.bodies[1] && (this.bodies[1] as HTMLElement).offsetTop === value) {
            //如果发生了掉头,让蛇向反方向继续移动
            if (value > this.y) {
                value = this.y - 10
            } else {
                value = this.y + 10
            }


            
        }



         // 移动身体
         this.moveBody();

        this.header.style.top = value +'px'
        //检查有没有撞到自己
        this.checkHeaderBody()

    }

    //设置蛇自增长
    addBody(){
        //从后增长
        this.element.insertAdjacentHTML('beforeend','<div></div>')

    }

    //添加蛇移动身体的方法
    moveBody(){
        /*
        *将后边的身体设置为前边身体的位置
        *
        * */
        for (let i = this.bodies.length-1; i > 0; i--) {
            //获取前边身体的位置
            let x = (this.bodies[i-1] as HTMLElement).offsetLeft;
            let y = (this.bodies[i-1] as HTMLElement).offsetTop;
            //将值设置到当前的身体上
            (this.bodies[i] as HTMLElement).style.left = x +'px';
            (this.bodies[i] as HTMLElement).style.top = y +'px';
            
        }


    }

    
    //检查头跟身体有没有相撞
    checkHeaderBody(){
        //获取所有的身体,检查是否蛇头和身体的坐标发生重叠
        for (let i = 1; i < this.bodies.length; i++){
            let bd = this.bodies[i] as HTMLElement        
            if (this.x === bd.offsetLeft && this.y === bd.offsetTop) {
                //进入判断说明蛇头撞到了身体,游戏结束
                throw new Error("撞到自己了");
                
            }

        }

    }



}

export default Snake